#define _CRT_SECURE_NO_WARNINGS 1
#pragma once
#include<iostream>
#include <utility>
#include<assert.h>
class String
{
public:
	typedef char* iterator;
public:
	String(const char* cp="")
	{
		size_=strlen(cp);
		capacity_ = size_;
		str_ = new char[strlen(cp) + 1];
		strcpy(str_,cp);
	}
	String(const String& cp):str_(nullptr),size_(0),capacity_(0)
	{
		if (this!=&cp)
		{
			String tmp(cp.str_);//本质上还是调用 上面的char* 构造函数 只是因为swap不能直接交换const类型
			//std::swap(str_,cp.str_);这是错误的
			swap(tmp);
		}
	}
	void swap(String& cp)
	{
		std::swap(str_,cp.str_);
		std::swap(size_,cp.size_);
		std::swap(capacity_,cp.capacity_);
	}
	String& operator=(const String& cp)
	{
		if (this != &cp)
		{
			String tmp(cp.str_);//同拷贝构造
			swap(tmp);
		}
		return *this;
	}
	~String()
	{
		if (str_)
		{
			delete[] str_;
			size_ = capacity_ = 0;
			str_ = nullptr;
		}
	}
	///////////////////////////////////////////////////////
	//iterator
	iterator begin()
	{
		return str_;
	}
	iterator end()
	{
		return str_ + size_;
	}
	//////////////////////////////////////////////////////
	//put an pop
	void push_back(const char ch)
	{
		while (size_>=capacity_)//大可不必 因为这种连续非链表结构的 都是一个一个添加的
		{
			reserve(capacity_*2);
		}
		str_[size_] = ch;
		size_++;
		str_[size_] = '\0';
	}
	String& operator+=(const char ch)
	{
		push_back(ch);
		return *this;
	}
	void append(const char* ap)
	{
		for (size_t i=0;i<strlen(ap);i++)
		{
			this->push_back(ap[i]);
		}
	}
	String& operator+=(const char* ap)
	{
		for (size_t i = 0; i < strlen(ap); i++)
		{
			this->push_back(ap[i]);
		}
		return *this;
	}
	/////////////////////////
	//tools
	void clear()
	{
		size_ = 0;
		str_[0] = '\0';//单纯置零！！！！！！！！！！！！！！
	}
	void reserve(size_t newcapacity)//扩容
	{
		if (newcapacity>capacity_)
		{
			char* tmp = new char[newcapacity];
			strcpy(tmp,str_);
			capacity_ = newcapacity;
		}
	}
	size_t size()const
	{
		return size_;
	}
	size_t capacity()const
	{
		return capacity_;
	}
	bool empty()
	{
		return size()==0;
	}
	//////////////////////////
	//access
	const char& operator[](size_t pos)const
	{
		assert(pos<size_);
		return str_[pos];
	}
	char& operator[](size_t pos)
	{
		assert(pos < size_);
		return str_[pos];
	}
	private:
		friend std::ostream& operator<<(std::ostream& cout_, const String& s);//在public 和 private 都可以

		friend std::istream& operator>>(std::istream& cin_, String& s);

private:
	char* str_;
	size_t size_;
	size_t capacity_;
};
//关于重载：这里就单做演示 实际还有>= ==等重载，但是最关键的重载是流插入和流提取的重载
std::ostream& operator<<(std::ostream& cout_,const String& s)
{
	//cout_ << s.str_;
	for (int i=0;i<s.size_;i++)//这里出现了一点点bug 遇到'\0'就不打印了
	{
		cout_ << s.str_[i];
	}
	return cout_;
}
std::istream& operator>>(std::istream& cin_,String& s)
{
	for (int i=0;i<s.size_;i++)
	{
		cin_ >> s.str_[i];
	}
	return cin_;
}
//test code
int main()
{
	String s = "hello\0yehao";
	char ch = s[1];
	std::cin >> s;
	std::cout << s<<std::endl;
	
	return 0;
}